package ar.com.siglo21.algoritmos.model;

import ar.com.siglo21.algoritmos.exception.ListaEnlazadaDobleException;

public class ListaEnlazadaDobleIter implements ListaIteradora {

	private ListaDoblementeEnlazada laLista;
	private NodoDoble actual;

	public ListaEnlazadaDobleIter(ListaDoblementeEnlazada unaLista) {
		laLista = unaLista;
		actual = laLista.esVacia() ? unaLista.getPrimero() : unaLista
				.getPrimero().getSiguiente();

	}

	public void avanzar() {
		if (actual != laLista.getUltimo()) {
			actual = actual.getSiguiente();
		}

	}

	public NodoDoble getActual() {
		return actual;
	}

	public void setActual(NodoDoble actual) {
		this.actual = actual;
	}

	@Override
	public void insertar(DatoNodo datoNodo) throws ListaEnlazadaDobleException {
		if (actual == null) {
			throw new ListaEnlazadaDobleException("Error en insercion");
		}
		NodoDoble nuevoNodo = new NodoDoble(datoNodo, actual.getSiguiente(),
				actual);
		actual.getSiguiente().setAnterior(nuevoNodo);
		actual.setSiguiente(nuevoNodo);
		actual.setDatoNodo(datoNodo);
		actual = nuevoNodo;
	}

	public boolean estaDentro() {

		return actual != laLista.getUltimo() && actual != laLista.getPrimero();
	}

	public DatoNodo recuperar() {

		return estaDentro() ? (actual).getDatoNodo() : null;
	}

	public void cero() {
		actual = laLista.getPrimero();
	}

	public void primero() {
		actual = laLista.getPrimero().getSiguiente();
	}

	@Override
	public void imprimir() {
		NodoDoble actual;
		actual = laLista.getPrimero();
		while (actual != laLista.getUltimo()) {
			actual = actual.getSiguiente();
			System.out.println(actual.getDatoNodo().getNombreArchivo());
		}
	}

	@Override
	public String imprimirDocumentos() {
		NodoDoble actual;
		actual = laLista.getPrimero();
		String documentos = "";
		while (actual != laLista.getUltimo()) {
			if (actual.getDatoNodo() != null) {
				documentos += actual.getDatoNodo().getNombreArchivo()
						.concat("-");
				actual = actual.getSiguiente();
			}
		}
		return documentos;
	}

	public void insertarAscendente(Comparable<Object> x) {
		ListaEnlazadaDobleIter ant = new ListaEnlazadaDobleIter(laLista);
		ListaEnlazadaDobleIter act = new ListaEnlazadaDobleIter(laLista);

		if (laLista.esVacia()) {
			try {
				ant.insertar((DatoNodo) x);
			} catch (ListaEnlazadaDobleException e) {
				e.printStackTrace();
			}
		} else {
			ant.cero();
			act.primero();

			while (act.estaDentro()
					&& (((DatoNodo) act.recuperar()).compareTo(x) <= 0)) {
				ant.avanzar();
				act.avanzar();
			}
			try {
				ant.insertar((DatoNodo) x);
				setActual(ant.getActual());
			} catch (ListaEnlazadaDobleException e) {
				e.printStackTrace();
			}
		}
	}

	public void insertarDescendente(Comparable<Object> x) {
		ListaEnlazadaDobleIter ant = new ListaEnlazadaDobleIter(laLista);
		ListaEnlazadaDobleIter act = new ListaEnlazadaDobleIter(laLista);

		if (laLista.esVacia()) {
			try {
				ant.insertar((DatoNodo) x);
			} catch (ListaEnlazadaDobleException e) {
				e.printStackTrace();
			}
		} else {
			ant.cero();
			act.primero();

			while (act.estaDentro()
					&& (((DatoNodo) act.recuperar()).compareTo(x) >= 1)) {
				ant.avanzar();
				act.avanzar();
			}
			try {
				ant.insertar((DatoNodo) x);
				setActual(ant.getActual());
			} catch (ListaEnlazadaDobleException e) {
				e.printStackTrace();
			}
		}
	}

}
